/******************************************************************
 *
 *    三七信产
 *
 *    Copyright (c) 2021-2023
 *
 *    Package:     org.jeecg.modules.sva.util
 *
 *    Filename:    SQStringUtil.java
 *
 *    Description: 
 *
 *    Copyright:   Copyright (c) 2021-2023
 *
 *    Company:     三七信产
 *
 *    @author:     duany
 *
 *    @version:    1.0.0
 *
 *    Create at:   2023-06-06 14:38:33
 *
 *    Revision:
 *
 *    2023-06-06 14:38:33 - first revision by duany
 *
 *    Function List:
 *
 *****************************************************************/

package com.sanqi.common.utils;

import java.io.BufferedWriter;
import java.io.FileWriter;
import java.io.IOException;
import java.io.PrintWriter;
import java.io.StringWriter;
import java.math.BigInteger;
import java.security.NoSuchAlgorithmException;
import java.security.SecureRandom;
import java.util.Random;
import java.util.regex.Pattern;

import javax.crypto.KeyGenerator;
import javax.crypto.SecretKey;

import org.apache.commons.codec.binary.Base64;

import cn.hutool.core.date.DateUtil;
import cn.hutool.core.util.ReUtil;
import cn.hutool.core.util.StrUtil;

/**
 * @ClassName SQStringUtil
 * @Description 
 * @author duany
 * @Date 2023-06-06 14:38:33
 * @version 1.0.0
 */

public class SQStringUtil {
    /**
     * @Description 姓名模糊化
     * @param name
     * @return
     * Create at: 2023-06-06 14:55:53
     * @author: duany
     * Revision:
     *    2023-06-06 14:55:53 - first revision by duany
     *        
     */
    public static String nameDesensitization(String name) {
        if(StrUtil.isBlank(name)) {
            return StrUtil.EMPTY;
        }
        name = name.trim();
        int length = StrUtil.length(name);
        String last = StrUtil.subSuf(name, length - 1);
        
        return asterisk(length-1) + last;
    }
    
    /**
     * @Description 电话模糊化
     * @param phone
     * @return
     * Create at: 2023-06-06 14:55:56
     * @author: duany
     * Revision:
     *    2023-06-06 14:55:56 - first revision by duany
     *        
     */
    public static String phoneDesensitization(String phone) {
        if(StrUtil.isBlank(phone)) {
            return StrUtil.EMPTY;
        }
        phone = phone.trim();
        int length = StrUtil.length(phone);
        String last = StrUtil.subSuf(phone, length - 4);
        
        String middle = asterisk(4);
        String top = StrUtil.sub(phone, 0, length-8);
        
        return StrUtil.builder(top, middle, last).toString();
    }
    
    /**
     * @Description 身份证号脱敏
     * @param cardNo
     * @return
     * Create at: 2023-06-07 10:47:31
     * @author: duany
     * Revision:
     *    2023-06-07 10:47:31 - first revision by duany
     *        
     */
    public static String idCardNoDesensitization(String cardNo) {
        if(StrUtil.isBlank(cardNo)) {
            return StrUtil.EMPTY;
        }
        cardNo = StrUtil.trim(cardNo);
        int length = StrUtil.length(cardNo);
        
        String last = StrUtil.subSuf(cardNo, length - 3);
        
        String middle = asterisk(12);
        String top = StrUtil.sub(cardNo, 0, length-15);
        return StrUtil.builder(top, middle, last).toString();
    }
    
    public static String messageDesensitization(String message) {
        if(StrUtil.isBlank(message)) {
            return StrUtil.EMPTY;
        }
        if(StrUtil.contains(message, "身份证")) {
            String regex ="([1-9]\\d{5}(18|19|20)\\d{2}((0[1-9])|(10|11|12))(([0-2][1-9])|10|20|30|31)\\d{3}[0-9Xx])|([1-9]\\d{5}\\d{2}((0[1-9])|(10|11|12))(([0-2][1-9])|10|20|30|31)\\d{3})";
            Pattern pattern = Pattern.compile(regex);
            String group0 = ReUtil.getGroup0(pattern, message);
            if(StrUtil.isNotBlank(group0)) {
                message = StrUtil.replace(message, group0, "");
            }
        }
        if(StrUtil.contains(message, "号码")) {
            String numberReg = "((13[0-9])|(15[^4])|(18[0,2,3,5-9])|(17[0-8])|(147)|(19[0-9]))\\d{8}";
            Pattern numberPattern = Pattern.compile(numberReg);
            String group0 = ReUtil.getGroup0(numberPattern, message);
            if(StrUtil.isNotBlank(group0)) {
                message = StrUtil.replace(message, group0, phoneDesensitization(group0));
            }
        }
        
        return message;
    }
    
    private static String asterisk(int num) {
        StringBuilder builder = StrUtil.builder("");
        for (int i = 0; i < num; i++) {
            builder.append("*");
        }
        return builder.toString();
    }
    
    public static boolean addTxtStr(String filePath, String info) {
        try {
            // 创建一个新的文件写入器
            BufferedWriter writer = new BufferedWriter(new FileWriter(filePath, true));
 
            // 写入新行内容
            writer.write(info);
            writer.newLine();
 
            // 关闭写入器
            writer.close();
            return true;
        } catch (IOException e) {
            System.out.println("添加新行到文件时发生错误：" + e.getMessage());
        }
        return false;
    }
    
    public static String getRandomString(int length) {
        StringBuilder sb = new StringBuilder("");
        Random random = new Random();
        char[] chars = {'0','1','2','3','4','5','6','7','8','9','a','b','c','d','e','f','g','h','i','j','k','l','m','n','o'
                ,'p','q','r','s','t','u','v','w','x','y','z'};
        for (int i = 0; i < length; i++) {
            int a = random.nextInt(36);
            sb.append(chars[a]);
        }
        return sb.toString();
    }
    
    /**
     * @Description 
     * @param aesType 128, 192或256
     * @return
     * Create at: 2024-06-07 10:11:04
     * @author: duany
     * Revision:
     *    2024-06-07 10:11:04 - first revision by duany
     *        
     */
    public static String genAesSecret(int aesType){
        try {
            KeyGenerator kg = KeyGenerator.getInstance("AES");
            //下面调用方法的参数决定了生成密钥的长度，可以修改为128, 192或256
            kg.init(aesType);
            SecretKey sk = kg.generateKey();
            byte[] b = sk.getEncoded();
            String secret = Base64.encodeBase64String(b);
            return secret;
        }
        catch (NoSuchAlgorithmException e) {
            e.printStackTrace();
            return null;
        }
    }
    
    /**
     * @Description 获取错误字符串
     * @param e
     * @return
     * Create at: 2024-09-11 09:37:26
     * @author: duany
     * Revision:
     *    2024-09-11 09:37:26 - first revision by duany
     *        
     */
    public static String getExceptionString(Exception e) {
        if(null == e) {
            return "";
        }
        StringWriter errors = new StringWriter();
        e.printStackTrace(new PrintWriter(errors));
        return errors.toString();
    }
    
    /**
     * @Description 获取Secret
     * @return
     * Create at: 2024-11-28 16:12:22
     * @author: duany
     * Revision:
     *    2024-11-28 16:12:22 - first revision by duany
     *        
     */
    public static String getAppSecrettring(int length) {
        String characters = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789";
        SecureRandom random = new SecureRandom();
        StringBuilder secret = new StringBuilder(length);
        for (int i = 0; i < length; i++) {
            secret.append(characters.charAt(random.nextInt(characters.length())));
        }
        return secret.toString();
    }
    
    /**
     * @Description 生成随机数字
     * @param length
     * @return
     * Create at: 2024-12-25 17:33:31
     * @author: duany
     * Revision:
     *    2024-12-25 17:33:31 - first revision by duany
     *        
     */
    public static String getRandomNotring(int length) {
        Random random = new Random();
        String numStr = "";
        for (int i = 0; i < length; i++) {
            numStr = numStr + "9";
        }
        // 生成一个0到999999之间的随机数
        long randomNumber = random.nextLong(Long.valueOf(numStr));
        String formattedNumber = String.format("%0" + (length) + "d", randomNumber);
        return formattedNumber;
    }
    
    public static String huashuUserId(String cardNo) {
        String subSufByLength = StrUtil.subSufByLength(cardNo, 6);
        String dateStr = DateUtil.format(DateUtil.date(), "yyyyMMdd");
        return subSufByLength + dateStr + getRandomNotring(6);
    }
    
    public static String getStrFirstNumber(String str) {
        String numberStr = "";
        if(null == str) {
            return numberStr;
        }
        if(str.isBlank()) {
            return numberStr;
        }
        boolean flag = false;
        char[] charArray = str.toCharArray();
        for(int i = 0; i < charArray.length; i++) {
            char c = charArray[i];
            if(c >= '0' && c<= '9') {
                if(flag == false) {
                    flag = true;
                }
                numberStr += c;
            } else {
                if(flag) {
                    break;
                }
            }
        }
        
        return numberStr;
    }
    
    private static int id_index = 1;
    private static long time_millis = 0;
    /**
     * 生成主键字符串
     * @return
     */
    public static String getSnowflakeStr() {
        synchronized(SQStringUtil.class){
            long timeMillis = System.currentTimeMillis();
            if(timeMillis-time_millis > 7000) {
                time_millis = timeMillis;
                id_index = 1;
            }
            BigInteger aa = new BigInteger(String.valueOf(timeMillis));
            aa = aa.multiply(new BigInteger("4194304"));
            aa = aa.add(new BigInteger(String.valueOf(id_index & 0x3FFFFF)));
            id_index ++;
            return  String.valueOf(aa.toString());
        }
    }
}
